﻿using Kingdee.BOS.Core.Bill;
using Kingdee.BOS.Core;
using Kingdee.BOS.Core.Bill.PlugIn;
using Kingdee.BOS.Core.Const;
using Kingdee.BOS.Core.DynamicForm;
using Kingdee.BOS.Core.DynamicForm.PlugIn.Args;
using Kingdee.BOS.Core.Interaction;
using Kingdee.BOS.Core.List;
using Kingdee.BOS.Core.Metadata.ConvertElement.ServiceArgs;
using Kingdee.BOS.Core.Metadata.ConvertElement;
using Kingdee.BOS.Core.Metadata;
using Kingdee.BOS.Orm;
using Kingdee.BOS.ServiceHelper;
using Kingdee.BOS.Util;
using System;
using System.Collections.Generic;
using System.ComponentModel;
using System.Linq;
using System.Text;
using Kingdee.BOS.Orm.DataEntity;
using Newtonsoft.Json;
using Kingdee.BOS.Core.Metadata.ConvertElement.PlugIn;
using Kingdee.BOS.Core.Metadata.ConvertElement.PlugIn.Args;
using Kingdee.BOS.Core.Metadata.EntityElement;

namespace Kingdee.SR.Plugin
{
    [Description("【单据插件】测试单据转换"), HotUpdate]
    public class TestPushPlugIn : AbstractBillPlugIn
    {
        //F_WSWB_Button
        public override void ButtonClick(ButtonClickEventArgs e)
        {
            base.ButtonClick(e);
            if (e.Key.EqualsIgnoreCase("F_WSWB_Button"))
            {
                OperateOption pushOption = OperateOption.Create();//操作选项
                var pushArgs = this.CreatePushArgs(pushOption); //构建下推参数
                                                                //  Tools.WriteLog.Write($"pushArgs :\\r\\n {JsonConvert.SerializeObject(pushArgs)}");
                var convertResult = ConvertServiceHelper.Push(this.Context, pushArgs, pushOption);//调用下推接口
                                                                                                  //   Tools.WriteLog.Write($"convertResult :\\r\\n {JsonConvert.SerializeObject(convertResult)}");
                var targetObjs = (from p in convertResult.TargetDataEntities select p.DataEntity).ToArray();//得到目标单据数据包
                                                                                                            //  Tools.WriteLog.Write($"targetObjs :\\r\\n {JsonConvert.SerializeObject(targetObjs)}");
                var targetBInfo = this.GetBusinessInfo(pushArgs.ConvertRule.TargetFormId, pushArgs.ConvertRule.TargetFormMetadata);
                //   Tools.WriteLog.Write($"targetBInfo :\\r\\n {JsonConvert.SerializeObject(targetBInfo)}");
                //对转换结果进行处理
                //1. 直接调用保存接口，对数据进行保存
                //   this.SaveTargetBill(targetBInfo, targetObjs);
                //2. 或者展示目标单据
                this.ShowTargetForm(targetBInfo, targetObjs);
            }
        }

        private void SaveTargetBill(BusinessInfo targetBusinessInfo, DynamicObject[] targetBillObjs)
        {
            OperateOption saveOption = OperateOption.Create();
            saveOption.SetIgnoreWarning(true);
            saveOption.SetIgnoreInteractionFlag(true);
            var saveResult = BusinessDataServiceHelper.Save(this.Model.Context, targetBusinessInfo, targetBillObjs, saveOption);
            if (!saveResult.IsSuccess)
            {
                var errorInfo = string.Join(";", saveResult.ValidationErrors.Select(x => x.Message));
                this.View.ShowErrMessage(errorInfo);
                return;
            }
            else
            {
                this.View.ShowMessage("生成成功");
            }
        }
        /// <summary>
        /// 创建下推参数
        /// </summary>
        /// <returns></returns>
        private PushArgs CreatePushArgs(OperateOption pushOption)
        {
            //得到转换规则
            var convertRule = this.GetConvertRule();
            //源单数据
            // var selectedRow = this.GetSelectedRow(pushOption);

            //ListSelectedRow sr = new ListSelectedRow(primaryKeyValue, entryPrimaryKeyValue, rowKey,  sourceFormId);

            List<ListSelectedRow> selectedRows = new List<ListSelectedRow>();
            ListSelectedRow sr = new ListSelectedRow("100001", "100001", 0, "PRD_MO");
            // selectedRows.Add(sr);

            //sr = new ListSelectedRow("101001", "101501", 0, "PRD_MO");
            //selectedRows.Add(sr);
            sr = new ListSelectedRow("100041", "100055", 0, "SAL_SaleOrder");
            selectedRows.Add(sr);

            //单据下推参数
            PushArgs pushArgs = new PushArgs(convertRule, selectedRows.ToArray());
            //目标单据主组织，可选参数，基础资料隔离，给没有住组织的目标数据包赋值，取当前登录组织即可
            //pushArgs.TargetOrgId = this.Context.CurrentOrganizationInfo.ID;
            //目标单据类型，必填参数，除非下游单据类型不是必填的，对源单数据进行过滤，给目标单赋值
            pushArgs.TargetBillTypeId = "83d822ca3e374b4ab01e5dd46a0062bd";
            return pushArgs;
        }
        /// <summary>
        /// 展示目标单据
        /// </summary>
        private void ShowTargetForm(BusinessInfo targetBusinessInfo, DynamicObject[] targetBillObjs)
        {
            BillShowParameter param = new BillShowParameter();
            param.ParentPageId = this.View.PageId;
            if (targetBillObjs.Length == 1)
            {
                param.Status = OperationStatus.ADDNEW;
                param.CreateFrom = CreateFrom.Push;
                param.AllowNavigation = false;
                string sessionKey = FormConst.ConvParamKey_OneResultSessionKey;// "_ConvertSessionKey";
                string sessionName = FormConst.ConvParamKey_OneResultSessionName;// "ConverOneResult";
                param.CustomParams.Add(sessionKey, sessionName);
                this.View.Session[sessionName] = targetBillObjs[0];       // 把结果放在交换区，供子页面取用
                //param.FormId = targetBusinessInfo.GetForm().Id; //formID
                param.FormId = "PUR_PurchaseOrder"; //formID

            }
            else if (targetBillObjs.Length > 1)
            {
                param.FormId = FormIdConst.BOS_ConvertResultForm;
                string sessionName = FormConst.ConvParamKey_ResultSessionName;//"ConvertResults";
                this.View.Session[sessionName] = targetBillObjs;       // 把结果放在交换区，供子页面取用
                //param.CustomParams.Add(FormConst.ConvParamKey_TargetFormId, targetBusinessInfo.GetForm().Id);
                param.CustomParams.Add(FormConst.ConvParamKey_TargetFormId, "PUR_PurchaseOrder");
            }
            else
            {
                //没有数据时直接返回
                return;
            }
            param.CustomParams.Add("_pickId", "sr123456798");
            param.OpenStyle.ShowType = ShowType.MainNewTabPage;
            this.View.ShowForm(param);
        }
        // 得到下推数据行，有下面四种构建方式，按需求选择所需要的构建方式
        private ListSelectedRow[] GetSelectedRow(OperateOption pushOption)
        {
            //1. 列表页面，按分录下推
            if (this.View is IListViewService)
            {
                var listView = this.View as IListView;
                if ((listView.SelectedRowsInfo == null) || (listView.SelectedRowsInfo.Count == 0))
                {
                    var msg = "请选择下推数据行！";
                    this.View.ShowMessage(msg);
                }
                pushOption.SetVariableValue(ConvertConst.SelectByBillId, false);
                var res = listView.SelectedRowsInfo.ToArray();
                return res;
            }
            else //2. 单据维护界面,按整单下推
            {
                var billView = this.View as IBillView;
                string primaryKeyValue = billView.Model.GetPKValue().ToString();
                ListSelectedRow row = new ListSelectedRow(primaryKeyValue, string.Empty, 0, billView.BillBusinessInfo.GetForm().Id);
                return new ListSelectedRow[] { row };
            }
            //或者自行创建下推数据行
            //3. 自定义按分录下推
            List<ListSelectedRow> selectedRows = new List<ListSelectedRow>();
            var selectedRow = new ListSelectedRow(string.Empty, "单据体内码", 0, "表单formId");
            selectedRow.EntryEntityKey = "单据体key"; //这里最容易忘记加，是重点的重点
            pushOption.SetVariableValue(ConvertConst.SelectByBillId, false);
            selectedRows.Add(selectedRow);
            //4. 自定义整单下推
            List<ListSelectedRow> selectedRows1 = new List<ListSelectedRow>();
            var selectedRow1 = new ListSelectedRow("单据内码", "", 0, "表单formId");
            pushOption.SetVariableValue(ConvertConst.SelectByBillId, true);
            selectedRows.Add(selectedRow);
        }
        //得到转换规则
        private ConvertRuleElement GetConvertRule()
        {
            var convertRuleId = "SaleOrder-POOrder";//19277421-9b54-49ae-b2a6-787630ce6c05
            var convertRuleMeta = ConvertServiceHelper.GetConvertRule(this.Context, convertRuleId);
            return convertRuleMeta.Rule;
        }
        // 得到表单元数据
        private BusinessInfo GetBusinessInfo(string formId, FormMetadata metaData = null)
        {
            if (metaData != null) return metaData.BusinessInfo;

            BusinessInfo businessInfo = new BusinessInfo();
            return businessInfo;
            metaData = FormMetaDataCache.GetCachedFormMetaData(this.Context, formId);
            return metaData.BusinessInfo;
        }

    }

    [Description(" 下推采购订单初始化数据")]
    [HotUpdate]
    public class Prd_InStock_Push_InitData : AbstractBillPlugIn
    {
        string _pickId = "";
        string _moId = "";

        public override void OnInitialize(InitializeEventArgs e)
        {
            base.OnInitialize(e);
            _pickId = e.Paramter.GetCustomParameter("_pickId") + "";
            _moId = e.Paramter.GetCustomParameter("_moId") + "";
           
        }

        public override void BeforeBindData(EventArgs e)
        {
            base.BeforeBindData(e);
            if (!string.IsNullOrWhiteSpace(_pickId))
            {
                this.View.ShowMessage($"_pickId:{_pickId} ,_moId:{_moId}");
                WriteLog.Write("BeforeBindData");

                this.View.Model.DeleteEntryRow("FPOOrderEntry", 0);

                Entity entryEntity = this.View.Model.BusinessInfo.GetEntity("FPOOrderEntry");

                DynamicObjectCollection entryRows = this.View.Model.GetEntityDataObject(entryEntity);

                this.View.Model.CreateNewEntryRow("FPOOrderEntry");
                int lastRowIndex = entryRows.Count - 1;
                this.Model.SetValue("FQty", "111", lastRowIndex);
                this.Model.SetValue("FMaterialId", "100322", lastRowIndex);
            }
        }

        public override void AfterBindData(EventArgs e)
        {
            base.AfterBindData(e);
            //if (!string.IsNullOrWhiteSpace(_pickId))
            //{
                WriteLog.Write("AfterBindData123");
                //DynamicObjectCollection a = this.View.Model.GetEntityDataObject(this.View.Model.BusinessInfo.Entrys[3]);
                //WriteLog.Write(JsonConvert.SerializeObject(a));
                //a[0]["Qty"] = 123;
                //a = this.View.Model.GetEntityDataObject(this.View.Model.BusinessInfo.Entrys[3]);
                //WriteLog.Write(JsonConvert.SerializeObject(a));

             

               
                 

        

                //更新单据体

               // this.View.UpdateView("FPOOrderEntry");

                //this.View.Model.SetValue("MustQty", 999, 0);
                //this.View.Model.DeleteEntryRow("Entity", 0);
                //this.View.Model.BusinessInfo.Entrys.Clear();
                //this.View.Model.SetValue("Entity", "430701", 0);
            //}
        }

        public override void OnLoad(EventArgs e)
        {
            base.OnLoad(e);
            if (!string.IsNullOrWhiteSpace(_pickId))
            {
                WriteLog.Write("OnLoad");
            }
        }
    }

    [Description("【单据转换插件】 采购订单"), HotUpdate]

    public class POOrderCovertPlugIn : AbstractConvertPlugIn
    {
        public override void OnGetSourceData(GetSourceDataEventArgs  e)
        {
            base.OnGetSourceData(e);
            var list = ObjectUtils.CreateCopy(e.SourceData) as DynamicObjectCollection;
            e.SourceData.Clear();

            foreach (DynamicObject data in list)
            {
                int num = Convert.ToInt32(data["FBaseUnitQty"]);
                if (num == 1)
                {
                    data["FGroupText"] = data["FEntity_FEntryID"].GetString();
                    continue;
                }
                WriteLog.Write(JsonConvert.SerializeObject(data));
                // 根据填写数量拆分
                for (int i = 0; i < num; i++)
                {
                    var copy = ObjectUtils.CreateCopy(data) as DynamicObject;
                    // 修改数量和分组字段
                    copy["FBaseUnitQty"] = 123;
                    //copy["FMaterialId"] = 100322;
                    //copy["FGroupText"] = copy["FEntity_FEntryID"].GetString() + "_" + (i + 1).ToString();
                    e.SourceData.Add(copy);
                }
               
            }
            WriteLog.Write(JsonConvert.SerializeObject(e.SourceData));


        }
        public override void AfterConvert(AfterConvertEventArgs e)
        {
            base.AfterConvert(e);
            var targetForm = e.TargetBusinessInfo.GetForm();
            if (targetForm.LinkSet == null
                || targetForm.LinkSet.LinkEntitys == null
                || targetForm.LinkSet.LinkEntitys.Count == 0)
            {
                return;
            }

            Entity entity = e.TargetBusinessInfo.GetEntity(targetForm.LinkSet.LinkEntitys[0].ParentEntityKey);
            Entity linkEntity = e.TargetBusinessInfo.GetEntity(targetForm.LinkSet.LinkEntitys[0].Key);
            HashSet<long> srcBillIds = new HashSet<long>();
            Dictionary<int, HashSet<long>> dctDataIndexToSrcBillId = new Dictionary<int, HashSet<long>>();
            var entryRows = e.Result.FindByEntityKey(entity.Key);
            foreach (var entryRow in entryRows)
            {
                int dataIndex = entryRow.DataEntityIndex;
                if (dctDataIndexToSrcBillId.ContainsKey(dataIndex) == false)
                {
                    dctDataIndexToSrcBillId.Add(dataIndex, new HashSet<long>());
                }
                
                var linkRows = linkEntity.DynamicProperty.GetValue(entryRow.DataEntity) as DynamicObjectCollection;

                foreach (var linkRow in linkRows)
                {
                    long srcBillId = Convert.ToInt64(linkRow["SBillId"]);
                    if (srcBillIds.Contains(srcBillId) == false)
                    {
                        srcBillIds.Add(srcBillId);
                    }

                    if (dctDataIndexToSrcBillId[dataIndex].Contains(srcBillId) == false)
                    {
                        dctDataIndexToSrcBillId[dataIndex].Add(srcBillId);
                    }
                }

            }
            var a = 1;
        }

    }
}
